package com.imgrate.migration.service;

import com.imgrate.migration.entity.OperationLog;
import com.imgrate.migration.repository.OperationLogRepository;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletRequest;
import java.time.LocalDateTime;
import java.util.List;

@Service
@RequiredArgsConstructor
@Slf4j
public class OperationLogService {
    private final OperationLogRepository operationLogRepository;
    
    public void log(String username, OperationLog.OperationType operationType, 
                   OperationLog.OperationModule module, String description, 
                   OperationLog.OperationResult result) {
        OperationLog logEntry = new OperationLog();
        logEntry.setUsername(username);
        logEntry.setOperationType(operationType.name());
        logEntry.setOperationModule(module.name());
        logEntry.setDescription(description);
        logEntry.setResult(result.name());
        logEntry.setCreatedAt(LocalDateTime.now());
        
        operationLogRepository.save(logEntry);
        log.info("操作日志记录: 用户={}, 操作={}, 模块={}, 描述={}, 结果={}", 
                username, operationType, module, description, result);
    }
    
    public void logWithError(String username, OperationLog.OperationType operationType, 
                            OperationLog.OperationModule module, String description, 
                            String ipAddress, String userAgent, String errorMessage) {
        OperationLog logEntry = new OperationLog();
        logEntry.setUsername(username);
        logEntry.setOperationType(operationType.name());
        logEntry.setOperationModule(module.name());
        logEntry.setDescription(description);
        logEntry.setResult(OperationLog.OperationResult.FAILURE.name());
        logEntry.setIpAddress(ipAddress);
        logEntry.setUserAgent(userAgent);
        logEntry.setCreatedAt(LocalDateTime.now());
        
        operationLogRepository.save(logEntry);
        log.error("操作日志记录(错误): 用户={}, 操作={}, 模块={}, 描述={}, 错误={}", 
                username, operationType, module, description, errorMessage);
    }
    
    public void logHttpRequest(String username, OperationLog.OperationType operationType, 
                              OperationLog.OperationModule module, String description, 
                              OperationLog.OperationResult result, HttpServletRequest request) {
        OperationLog logEntry = new OperationLog();
        logEntry.setUsername(username);
        logEntry.setOperationType(operationType.name());
        logEntry.setOperationModule(module.name());
        logEntry.setDescription(description);
        logEntry.setResult(result.name());
        if (request != null) {
            logEntry.setIpAddress(request.getRemoteAddr());
            logEntry.setUserAgent(request.getHeader("User-Agent"));
        }
        logEntry.setCreatedAt(LocalDateTime.now());
        
        operationLogRepository.save(logEntry);
        log.info("HTTP请求日志: 用户={}, 操作={}, 模块={}, 描述={}, 结果={}, IP={}", 
                username, operationType, module, description, result, 
                request != null ? request.getRemoteAddr() : "unknown");
    }
    
    public List<OperationLog> getAllLogs() {
        return operationLogRepository.findAll();
    }
    
    public List<OperationLog> getLogsByUsername(String username) {
        return operationLogRepository.findByUsername(username);
    }
    
    public List<OperationLog> getLogsByOperationType(String operationType) {
        return operationLogRepository.findByOperationType(operationType);
    }
    
    public List<OperationLog> getLogsByTimeRange(LocalDateTime start, LocalDateTime end) {
        return operationLogRepository.findByCreatedAtBetween(start, end);
    }
    
    public List<OperationLog> getLogsByUsernameAndTimeRange(String username, LocalDateTime start, LocalDateTime end) {
        // 这里可以使用自定义查询或者在内存中过滤
        // 为了简单起见，我们使用内存过滤
        List<OperationLog> allLogs = getAllLogs();
        return allLogs.stream()
                .filter(log -> log.getUsername() != null && log.getUsername().equals(username))
                .filter(log -> log.getCreatedAt() != null && 
                              !log.getCreatedAt().isBefore(start) && 
                              !log.getCreatedAt().isAfter(end))
                .collect(java.util.stream.Collectors.toList());
    }
}